package project06.adt;

import static java.lang.Math.random;
import static java.lang.System.out;
import static java.lang.System.err;

public class ColaEstatica implements Cola {

	private static final int TAM_PREDET = 50;
	private Object []cola;
	private int primer, ultimo, tam;
	
	public ColaEstatica(){
		cola = new Object[TAM_PREDET];
		this.tam = TAM_PREDET;
		primer = 0;
		ultimo = -1;
	}
	
	public ColaEstatica(int tam){
		cola = new Object[tam];
		this.tam = tam;
		primer = 0;
		ultimo = -1;
	}
	
	@Override
	public boolean encolar(Object obj) {
		try {
			if (estaLlena())
				throw new ColaLlenaException();
			ultimo = ++ultimo % tam;
			cola[ultimo] = obj;
		} catch (ColaLlenaException e) {
			err.println(e.getMessage() + " -- Indice: " + ultimo + 1);
			reDim();
			encolar(obj);
		} catch (Exception e) {
			return false;
		}
		return true;
	}

	@Override
	public Object desencolar() {
		Object aux = null;
		if (!estaVacia()) {
			aux = cola[primer];
			if (primer == ultimo)
				vaciar();
			else
				primer = (primer + 1) % tam;
		}
		return aux;
	}

	@Override
	public void vaciar() {
		primer = 0;
		ultimo = -1;
	}

	@Override
	public boolean estaVacia() {
		return (primer == 0 && ultimo == -1);
	}
	
	public boolean estaLlena(){
		return ((primer == 0 && ultimo == tam - 1) || 
				(primer == ultimo + 1 && ultimo != -1));
	}

	private void reDim(){
		tam = 2 * tam;
		Object []aux = new Object[tam];
		
		for(int i = 0; i < cola.length; i++)
			aux[i] = cola[i];
		cola = aux;
	}
	@Override
	public Object tope() {
		if(!estaVacia())
			return cola[primer];
		return null;
	}
	/**
	 * @param args
	 */
	public static void main(String[] args) {
		Cola c1 = new ColaEstatica();
		
		c1.encolar("A");
		c1.encolar("B");
		c1.encolar("C");
		
		int i = 0, n = 2600;
		while(i++ < n)
			c1.encolar(random() * 100 * i);
		
		c1.encolar("ULTIMO OBJETO");
		
		while(!c1.estaVacia())
			out.println(c1.desencolar());
	}
}
